﻿using System.Collections.Generic;
using System.Drawing;
using LevelEditor.Forms;
using LevelEditor.Document;
using System.Windows.Forms;

namespace LevelEditor.View
{
    public class DoUndoPencilTile : DoUndoNothing
    {
        struct TileData
        {
            public Point Location;
            public uint Value;
            public TileData(Point location, uint value)
            {
                Location = location;
                Value = value;
            }
        }

        #region Fields

        int LayerIndex;

        Rectangle TilePoints;
        Point TileSetStart;

        List<TileData> UndoData;

        #endregion

        #region Contructors

        public DoUndoPencilTile(MainForm form, Rectangle tilePoints, Point tileSetStart):base(form)
        {
            Cursor.Current = Cursors.WaitCursor;
            UndoData = new List<TileData>();
            LayerIndex = form.CurrentLayer;
            TilePoints = tilePoints;
            TileSetStart = tileSetStart;

            for (int y = 0; y < TilePoints.Height; ++y)
            {
                for (int x = 0; x < TilePoints.Width; ++x)
                {
                    Point point = new Point(TilePoints.X + x, TilePoints.Y + y);
                    if (point.X < form.Level.Layers[LayerIndex].Size.Width &&
                        point.Y < form.Level.Layers[LayerIndex].Size.Height)
                    {
                        UndoData.Add(new TileData(point,
                                form.Level.Layers[LayerIndex].Tiles[point.X + point.Y * 
                                form.Level.Layers[LayerIndex].Size.Width]));
                    }
                }
            }
            Cursor.Current = Cursors.Default;
        }

        #endregion

        #region Methods

        public override bool Do()
        {
            Layer layer = MainForm.Level.Layers[LayerIndex];
            Cursor.Current = Cursors.WaitCursor;
            if (MainForm.CurrentLayer != LayerIndex)
            {
                MainForm.CurrentLayer = LayerIndex;
                MainForm.Palette.ResetToCurrentLayer(MainForm);
            }
            PaletteControl pc = (MainForm.Palette.pc as PaletteControl);
            foreach (TileData td in UndoData)
            {
                layer.Tiles[td.Location.X + td.Location.Y * layer.Size.Width] =
                        pc.GetValueFromTilePoint(new Point(TileSetStart.X + td.Location.X -
                            TilePoints.X, TileSetStart.Y + td.Location.Y - TilePoints.Y));
            }
            MainForm.LayerViewControl.Invalidate();
            Cursor.Current = Cursors.Default;
            return base.Do();
        }

        public override void Undo()
        {
            Cursor.Current = Cursors.WaitCursor;
            Layer layer = MainForm.Level.Layers[LayerIndex];
            foreach (TileData td in UndoData)
            {
                layer.Tiles[td.Location.X + td.Location.Y * layer.Size.Width] = td.Value;
            }
            MainForm.LayerViewControl.Invalidate();
            Cursor.Current = Cursors.Default;
        }

        public override string ToString()
        {
            return "Pencil at " + TilePoints.ToString();
        }

        #endregion
    }
}
